package com.zlf.sb.demo.service;

import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingDeque;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * @author zlf
 * @description:
 * @time: 2022/7/13 10:18
 */
public class ThreadPoolService {

    /**
     * CPU 密集型：核心线程数 = CPU核数 + 1
     * <p>
     * IO 密集型：核心线程数 = CPU核数 * 2
     * <p>
     * 注意：IO密集型 （某大厂实战经验）
     * 核心线程数 = CPU核数 / (1 - 阻塞系数)
     * 例如阻塞系数为0.8 ,CPU核数为 4 ，则核心线程数为 20
     */
    private static final int DEFAULT_CORE_SIZE = Runtime.getRuntime().availableProcessors() * 2;
    private static final int MAX_QUEUE_SIZE = 100;
    private static final int QUEUE_INIT_MAX_SIZE = 200;
    private volatile static ThreadPoolExecutor executor;

    private ThreadPoolService() {
    }

    // 获取单例的线程池对象
    public static ThreadPoolExecutor getInstance() {
        if (executor == null) {
            synchronized (ThreadPoolService.class) {
                if (executor == null) {
                    executor = new ThreadPoolExecutor(DEFAULT_CORE_SIZE,// 核心线程数
                            MAX_QUEUE_SIZE, // 最大线程数
                            Integer.MAX_VALUE, // 闲置线程存活时间
                            TimeUnit.MILLISECONDS,// 时间单位
                            new LinkedBlockingDeque<Runnable>(QUEUE_INIT_MAX_SIZE),// 线程队列
                            Executors.defaultThreadFactory()// 线程工厂
                    );
                }
            }
        }
        return executor;
    }

    public void execute(Runnable runnable) {
        if (runnable == null) {
            return;
        }
        executor.execute(runnable);
    }

    // 从线程队列中移除对象
    public void cancel(Runnable runnable) {
        if (executor != null) {
            executor.getQueue().remove(runnable);
        }
    }

}